package com.javaio;

import java.io.IOException;
import java.io.RandomAccessFile;
import java.net.InetSocketAddress;
import java.nio.ByteBuffer;
import java.nio.channels.*;
import java.nio.channels.spi.SelectorProvider;
import java.util.Iterator;
import java.util.Set;

/**
 * @program: study
 * @className: NioTest
 * @description: TODO
 * @author: kukuxiahuni
 * @create: 2020-03-13 10:15
 * @version: v1.0
 **/
public class NioTest {

    public static void main(String[] args) throws IOException {
        NioTest nioTest = new NioTest();
        nioTest.test();
    }

    public void test() throws IOException {
        Selector selector = SelectorProvider.provider().openSelector();
        ServerSocketChannel serverSocketChannel = ServerSocketChannel.open();

        /**
         * 配置为非阻塞
         */
        serverSocketChannel.configureBlocking(false);
        /**
         * 绑定过端口地址
         */
        serverSocketChannel.bind(new InetSocketAddress(12000));

        /**
         * 注册感兴趣的事件到selector
         */
        serverSocketChannel.register(selector, SelectionKey.OP_ACCEPT);

        while (!Thread.currentThread().isInterrupted()) {
            int opNum = selector.select(100);

            Set<SelectionKey> selectionKeySet = selector.selectedKeys();
            Iterator<SelectionKey> iterator = selectionKeySet.iterator();

            while (iterator.hasNext()) {
                SelectionKey key = iterator.next();
                iterator.remove();

                if (key.isValid()) {

                    if (key.isAcceptable()) {
                        SocketChannel socketChannel = serverSocketChannel.accept();
                        socketChannel.configureBlocking(false);
                        socketChannel.register(selector, SelectionKey.OP_READ
                        );
                    }

                    if (key.isReadable()) {
                        SocketChannel socketChannel = (SocketChannel) key.channel();
                        ByteBuffer byteBuffer = ByteBuffer.allocate(1024);


                        int readBytes = socketChannel.read(byteBuffer);
                        if (readBytes > 0) {

                            /**
                             * 切换读写模式
                             *
                             */

                            byteBuffer.flip();
                            byte[] array = new byte[byteBuffer.remaining()];
                            byteBuffer.get(array);

                            String body = new String(array, "utf8");
                            System.out.println(body);
                            doWrite(socketChannel, "huang");
                        } else if (readBytes < 0) {
                            key.cancel();
                            socketChannel.close();
                        }
                    }


                }

            }


        }

        if (selector != null) {
            selector.close();
        }

    }

    private final void doWrite(SocketChannel socketChannel, String ack) throws IOException {

        ByteBuffer byteBuffer = ByteBuffer.wrap(ack.getBytes());
//        byteBuffer.flip();

        socketChannel.write(byteBuffer);


    }


    private final void testChannel() throws IOException {
        FileChannel fileChannel = new RandomAccessFile("SingleReactor.java", "rw").getChannel();
        fileChannel.position(fileChannel.size());
        fileChannel.write(ByteBuffer.wrap("hcc".getBytes()));
    }
}
